package worm

import (
    "cloud_worm/wormweb/controllers/ctrconfig"
    "github.com/astaxie/beego/logs"
    "fmt"
    "cloud_worm/util/uhttp"
    "time"
    "cloud_worm/util/umodels/mysqldb"
    "cloud_worm/util/umodels/mysqldb/dbmanager"
    "cloud_worm/util/uconst"
)

type RouteConfController struct {
    ctrconfig.LoginCtr
}

// 请求方式：https://{domain}:{port}//route/listconfig?page_count=&page=&status=
func (rc *RouteConfController) Get()  {
    rc.Manager()

    offset, limit := rc.DealPage()
    status, err := rc.GetInt("status", mysqldb.StatusAll)

    // 查询数据
    routeConf := &dbmanager.RouterConfig{}
    count, err := routeConf.SelectCount(status)
    if err != nil {
        logs.Error(fmt.Sprintf("get route config count error: %s", err.Error()))
        data := map[string]interface{}{"total": 0, "data": []dbmanager.RouterConfig{}}
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeSystemErr, "get count error.", data)
        rc.ServeJSON()
        return
    }
    if count == 0 {
        data := map[string]interface{}{"total": count, "data": []dbmanager.RouterConfig{}}
        rc.Data["json"] = uhttp.CreateOkResponse(data)
        rc.ServeJSON()
        return
    }

    routes, err := routeConf.SelectWithStatus(offset, limit, status)
    if err != nil {
        logs.Error(fmt.Sprintf("get route config error: %s", err.Error()))
        data := map[string]interface{}{"total": count, "data": []dbmanager.RouterConfig{}}
        rc.Data["json"] = uhttp.CreateOkResponse(data)
        rc.ServeJSON()
        return
    }

    data := map[string]interface{}{"total": count, "data": routes}
    rc.Data["json"] = uhttp.CreateOkResponse(data)
    rc.ServeJSON()
    return
}

// 插入一条记录
func (rc *RouteConfController) Insert() {
    rc.Manager()

    type InputInfo struct {
        Version             string  `json:"version"`
        ConfigUrl           string  `json:"config_url"`
        AccessSrv           string  `json:"access_srv"`
        Timeout             int     `json:"timeout"`
        HeartbeatTimeout    int     `json:"heartbeat_timeout"`
    }
    var input InputInfo
    if err := rc.Unmarshal(&input); err != nil {
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeReqBodyErr, err.Error(), nil)
        rc.ServeJSON()
        return
    }
    if input.Version == mysqldb.SelectStrAll || input.ConfigUrl == mysqldb.SelectStrAll || input.AccessSrv == mysqldb.SelectStrAll {
        logs.Warning(fmt.Sprintf("route config insert input params error."))
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeParamErr, "input params error", nil)
        rc.ServeJSON()
        return
    }

    if input.Timeout < uconst.TimeoutMin {
        input.Timeout = uconst.TimeoutDefault
    }
    if input.HeartbeatTimeout < uconst.TimeoutMin {
        input.HeartbeatTimeout = uconst.TimeoutDefault
    }

    // 检查去重
    route := &dbmanager.RouterConfig{
        Version: input.Version,
        ConfigUrl: input.ConfigUrl,
        ServerAddress: input.AccessSrv,
    }
    err := route.Read("version", "config_url", "server_address")
    if err == nil {             // read到结果，则结束
        logs.Warning("route config duplicate for input params.")
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeParamErr, "route config duplicate for input params.", nil)
        rc.ServeJSON()
        return
    }

    // 插入数据
    route = &dbmanager.RouterConfig{
        Version: input.Version,
        ConfigUrl: input.ConfigUrl,
        ServerAddress: input.AccessSrv,
        IntervalTime: input.Timeout,
        HeartbeatTimeout: input.HeartbeatTimeout,
        Created: time.Now().Unix(),
    }
    route.Updated = time.Now().Unix()
    err = route.Insert()
    if err != nil {
        logs.Error(fmt.Sprintf("route config insert error: %s", err.Error()))
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeSystemErr, "route config insert error.", nil)
        rc.ServeJSON()
        return
    }

    rc.Data["json"] = uhttp.CreateOkResponse(nil)
    rc.ServeJSON()
    return
}

// 更新route config配置接口
func (rc *RouteConfController) Update() {
    rc.Manager()

    type InputInfo struct {
        Id                  int64   `json:"id"`
        Version             string  `json:"version"`
        ConfigUrl           string  `json:"config_url"`
        AccessSrv           string  `json:"access_srv"`
        Timeout             int     `json:"timeout"`
        HeartbeatTimeout    int     `json:"heartbeat_timeout"`
        Status              int     `json:"status"`
    }
    var input InputInfo
    if err := rc.Unmarshal(&input); err != nil {
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeReqBodyErr, err.Error(), nil)
        rc.ServeJSON()
        return
    }
    if input.Version == mysqldb.SelectStrAll || input.ConfigUrl == mysqldb.SelectStrAll || input.AccessSrv == mysqldb.SelectStrAll ||
        (input.Status != mysqldb.StatusValid && input.Status != mysqldb.StatusInvalid) {
        logs.Warning(fmt.Sprintf("route config update input params error."))
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeParamErr, "input params error", nil)
        rc.ServeJSON()
        return
    }
    if input.Timeout < uconst.TimeoutMin {
        input.Timeout = uconst.TimeoutDefault
    }
    if input.HeartbeatTimeout < uconst.TimeoutMin {
        input.HeartbeatTimeout = uconst.TimeoutDefault
    }

    // 先尝试读取
    route := &dbmanager.RouterConfig{Id: input.Id}
    err := route.Read("id")
    if err != nil {
        logs.Error(fmt.Sprintf("no this id route config: %d", input.Id))
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeParamErr, "no this id record.", nil)
        rc.ServeJSON()
        return
    }
    route.Version = input.Version
    route.ConfigUrl = input.ConfigUrl
    route.ServerAddress = input.AccessSrv
    route.IntervalTime = input.Timeout
    route.HeartbeatTimeout = input.HeartbeatTimeout
    route.Updated = time.Now().Unix()
    route.Status = input.Status
    err = route.Update("version", "config_url", "server_address", "interval_time", "heartbeat_timeout", "updated", "status")
    if err != nil {
        logs.Error(fmt.Sprintf("route config update error: %s", err.Error()))
        rc.Data["json"] = uhttp.CreateErrResponse(uhttp.RespCodeSystemErr, "route config update error.", nil)
        rc.ServeJSON()
        return
    }

    rc.Data["json"] = uhttp.CreateOkResponse(nil)
    rc.ServeJSON()
    return
}